package modelTest.threadBasedModel;

import java.awt.BorderLayout;
import java.awt.Canvas;
import java.awt.Color;
import java.awt.Dimension;
import java.awt.Font;
import java.awt.Graphics;
import java.awt.image.BufferStrategy;
import java.awt.image.BufferedImage;
import java.util.Iterator;

import javax.swing.JFrame;
import javax.swing.JPanel;

import modelTest.model.Coordinate;
import modelTest.test.testView2D.TestKeyPanel;
import modelTest.view.ScoreDrawer;
import modelTest.view.ViewParam;
import modelTest.view.scoreDrawers.TopLeftScoreDrawer;
import modelTest.view.view2D.Assets;

public class SinglePlayer2DFrame extends Canvas implements Runnable{
	
	private static final long serialVersionUID = -1722759515903792828L;
	private int width;
	private int height;
	private Color bkColor;
	
	private final long refreshWaitMillis = 10;
	
	private ThreadsBasedGameStatus status;
	private DrawableShipModel userShip;
	private DrawableShipController2D controller2d;
	private ScoreDrawer scoreDrawer;
	
	private BufferedImage shipSprite;
	private BufferedImage bulletSprite;
	private BufferedImage galaxyBackground;
	
	private BufferStrategy buffer;
	
	private Assets assets;
	
	public static void main(String[] args) {
		
		JFrame frame = new JFrame("Test view 2D of Thread based Model");
		frame.setResizable(false);
		JPanel mainPanel = new JPanel();
		mainPanel.setLayout(new BorderLayout());
		frame.getContentPane().add ( mainPanel );
		
		ThreadsBasedGameStatus status = new ThreadsBasedGameStatus();
		
		Concurrent2DThreadSpawner spawner = new Concurrent2DThreadSpawner(status, 1000, 200 , 5);
		
		//Modalita' in prova.
		ThreadBasedSinglePlayer singlePlayer = new ThreadBasedSinglePlayer( status, spawner );
		
		//Tasti per l'avvio dei mob.
		TestKeyPanel testKeyPanel = new TestKeyPanel( singlePlayer );
		mainPanel.add(testKeyPanel, BorderLayout.EAST);
		
		//Score
		Font scoreFont = Assets.getsLoader().getFont(Assets.FONT_SCORE, 96.0f);
		ScoreDrawer scoreDrawer = new TopLeftScoreDrawer( scoreFont, Color.YELLOW);
		
		//GamePanel!
		SinglePlayer2DFrame gamePanel = new SinglePlayer2DFrame( singlePlayer, scoreDrawer );
		mainPanel.add(gamePanel, BorderLayout.CENTER);
		
		frame.pack();
		frame.setLocationRelativeTo(null);
		frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
//		frame.setResizable(false);
		frame.setVisible(true);
		
		Thread gameThread = new Thread(gamePanel);
		gameThread.start();
		

	}
	

	public SinglePlayer2DFrame( ThreadBasedSinglePlayer singlePlayer, ScoreDrawer scoreDrawer ) {
		super();
		this.width = ViewParam.WIDTH;
		this.height = ViewParam.HEIGTH;
		this.bkColor = ViewParam.BACKGROUND_COLOR;
		
		this.status = singlePlayer.getStatus();
		this.scoreDrawer = scoreDrawer;
		userShip = status.getUserShip();
		controller2d = new DrawableShipController2D(userShip);
		assets = Assets.getsLoader();
		initSprites();
		initPanel();
		this.addKeyListener( controller2d );
	}
	
	private void initSprites(){
		shipSprite = assets.getAsset(Assets.SHIP_2D);
		bulletSprite = assets.getAsset(Assets.BULLET_AVIABLE_INDICATOR);
	}
	
	private void initPanel(){
		setFocusable(true);
		setPreferredSize(new Dimension(width, height));
		setBackground(bkColor);
	}
	
	public void setScoreDrawer(ScoreDrawer scoreDrawer) {
		this.scoreDrawer = scoreDrawer;
	}

	private void draw(){
		buffer = this.getBufferStrategy();
		if(buffer == null){
			createBufferStrategy(2);
			//Creato ora quindi sono tutti vuoti, non disegnerebbero nulla.
			return;
		}
		Graphics g = buffer.getDrawGraphics();
		g.setColor(bkColor);
		g.fillRect(0, 0, width, height);
		
		drawMobs(g);
		
		
		userShip.draw(g);
		
		drawGUI(g);
		
		g.dispose();
		buffer.show();
	}
	
	private void drawMobs(Graphics g){

		Iterator<String> IDs = status.getMobsMapSet().iterator();
		Coordinate coo;
		String ID;
		MobThread2D mob;
		
		while( IDs.hasNext() ){
			ID = IDs.next();
			mob = status.getMob( ID );
			mob.draw(g);
		}
	}
	
	private void drawGUI(Graphics g){
		drawBullets(g);
		
		
		//TODO
		long testScore = 999999L;
		scoreDrawer.drawScore(g, testScore);
	}
	
	private void drawBullets(Graphics g){
		int gapH = 20;
		int gapV = 4;
		int bulletX = 10;
		int bulletY = height-bulletSprite.getHeight()-gapH;
		for (int i = 0; i < userShip.getAviavailableAmmo() ; i++) {
			g.drawImage( bulletSprite, bulletX + gapH*i , bulletY + gapV*i, null );
		}
	}
	
	
	
	@Override
	public void run() {
		while(true){
//			repaint();
			draw();
			try {
				Thread.sleep(refreshWaitMillis);
			} catch (InterruptedException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
		}
	}
	
	@Override
	public void paint(Graphics g) {
		super.paint(g);
		draw();
	}
}
